﻿namespace Sai.Test
{
	using System.IO;
	using Sai.Core;
	using Xunit;
    using Sai.Test.XUnit;

	public class ProductReleaseProjectFacts
	{
		public class TheSaveToMethod
		{
			
			[Fact, InMemoryTest]
			public void Folder_Specified_Saves_In_Expected_Format()
			{
				var project = new ProductReleaseProject();
				project.Version = "1.0";

				project.Name = "My Lovely Product";

				project.FromVersion = "2009";
				project.FromFolder = "C:\\API\\2009";

				project.ToVersion = "2010";
				project.ToFolder = "C:\\API\\2010";

				project.OutputFolder = "C:\\API\\Output";

				string output = string.Empty;

				// should look like...
				//<SaiProject xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" Version="1.0" ID="b5dc9c0d-ac4d-42c3-9b26-be0f832f3d62">
				//  <FromVersion>2009</FromVersion>
				//  <FromFolder>C:\API\2009</FromFolder>
				//  <FromAssemblies />
				//  <ToFolder>C:\API\2010</ToFolder>
				//  <ToAssemblies />
				//  <ToVersion>2010</ToVersion>
				//  <OutputFolder>C:\API\Output</OutputFolder>
				//</SaiProject>
				using (var writer = new StringWriter())
				{
					project.SaveTo(writer);
					output = writer.ToString();
				}

				Assert.Contains("<SaiProject ", output);
				Assert.Contains("Version=\"1.0\"", output);
				Assert.Contains("Name=\"My Lovely Product\"", output);
				Assert.Contains("ID=\"", output);
				Assert.Contains("<FromVersion>2009</FromVersion>", output);
				Assert.Contains("<FromFolder>C:\\API\\2009</FromFolder>", output);
				Assert.Contains("<FromAssemblies />", output);
				Assert.Contains("<ToVersion>2010</ToVersion>", output);
				Assert.Contains("<ToFolder>C:\\API\\2010</ToFolder>", output);
				Assert.Contains("<ToAssemblies />", output);
				Assert.Contains("<OutputFolder>C:\\API\\Output</OutputFolder>", output);
			}

			
			[Fact, InMemoryTest]
			public void Output_Can_Be_Read_By_Builder()
			{
				ProductReleaseProject originalProject = new ProductReleaseProject();
				originalProject.Version = "1.0";

				originalProject.Name = "My Lovely Product";

				originalProject.FromVersion = "2009";
				originalProject.FromFolder = "C:\\API\\2009";

                for (int i = 0; i < 10; ++i)
                {
                    originalProject.AddFromFile(string.Format("c:\\FromFile{0}.dll", i + 1));
                }

				originalProject.ToVersion = "2010";
				originalProject.ToFolder = "C:\\API\\2010";

                for (int i = 0; i < 10; ++i)
                {
                    originalProject.AddToFile(string.Format("c:\\ToFile{0}.dll", i + 1));
                }

				originalProject.OutputFolder = "C:\\API\\Output";

				string output = string.Empty;

				using (var writer = new StringWriter())
				{
					originalProject.SaveTo(writer);
					output = writer.ToString();
				}

				ProductReleaseProject readProject = null;

				using (var reader = new StringReader(output))
				{
					var builder = new ProductReleaseProjectBuilder();
					readProject = builder.CreateFrom(reader);
				}

				Assert.NotNull(readProject);
				Assert.Equal(originalProject.ID, readProject.ID);
				Assert.Equal(originalProject.Version, readProject.Version);
				Assert.Equal(originalProject.Name, readProject.Name);
				Assert.Equal(originalProject.FromVersion, readProject.FromVersion);
				Assert.Equal(originalProject.FromFolder, readProject.FromFolder);
				Assert.Equal(originalProject.ToVersion, readProject.ToVersion);
				Assert.Equal(originalProject.ToFolder, readProject.ToFolder);
				Assert.Equal(originalProject.OutputFolder, readProject.OutputFolder);

                Assert.Equal(originalProject.FromAssemblies.Count, readProject.FromAssemblies.Count);
                Assert.Equal(originalProject.ToAssemblies.Count, readProject.ToAssemblies.Count);
            }

            // output saved relative
            // output saved does not save duplicates...

            [Fact, InMemoryTest]
            public void Output_Does_Not_Contain_Duplicates()
            {
                ProductReleaseProject originalProject = new ProductReleaseProject();
                originalProject.Version = "1.0";

                originalProject.Name = "My Lovely Product";

                originalProject.FromVersion = "2009";
                originalProject.FromFolder = "C:\\API\\2009";

                for (int i = 0; i < 10; ++i)
                {
                    originalProject.AddFromFile(string.Format("c:\\FromFile{0}.dll", i + 1));
                }

                // add twice...
                for (int i = 0; i < 10; ++i)
                {
                    originalProject.AddFromFile(string.Format("c:\\FromFile{0}.dll", i + 1));
                }

                originalProject.ToVersion = "2010";
                originalProject.ToFolder = "C:\\API\\2010";

                for (int i = 0; i < 10; ++i)
                {
                    originalProject.AddToFile(string.Format("c:\\ToFile{0}.dll", i + 1));
                }

                // add twice...
                for (int i = 0; i < 10; ++i)
                {
                    originalProject.AddToFile(string.Format("c:\\ToFile{0}.dll", i + 1));
                }

                originalProject.OutputFolder = "C:\\API\\Output";

                string output = string.Empty;

                using (var writer = new StringWriter())
                {
                    originalProject.SaveTo(writer);
                    output = writer.ToString();
                }

                ProductReleaseProject readProject = null;

                using (var reader = new StringReader(output))
                {
                    var builder = new ProductReleaseProjectBuilder();
                    readProject = builder.CreateFrom(reader);
                }

                Assert.NotNull(readProject);
                Assert.Equal(originalProject.FromAssemblies.Count, readProject.FromAssemblies.Count);
                Assert.Equal(originalProject.ToAssemblies.Count, readProject.ToAssemblies.Count);
            }

		}
	}
}
